package com.lekang.system.controller;

import java.util.List;
import javax.servlet.http.HttpServletResponse;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.lekang.common.annotation.Log;
import com.lekang.common.core.controller.BaseController;
import com.lekang.common.core.domain.AjaxResult;
import com.lekang.common.enums.BusinessType;
import com.lekang.system.domain.Bill;
import com.lekang.system.service.IBillService;
import com.lekang.common.utils.poi.ExcelUtil;
import com.lekang.common.core.page.TableDataInfo;

/**
 * 入账列表Controller
 * 
 * @author ruoyi
 * @date 2025-10-13
 */
@RestController
@RequestMapping("/system/bill")
public class BillController extends BaseController
{
    @Autowired
    private IBillService billService;

    /**
     * 查询入账列表列表
     */
    @PreAuthorize("@ss.hasPermi('system:bill:list')")
    @GetMapping("/list")
    public TableDataInfo list(Bill bill)
    {
        startPage();
        List<Bill> list = billService.selectBillList(bill);
        return getDataTable(list);
    }

    /**
     * 导出入账列表列表
     */
    @PreAuthorize("@ss.hasPermi('system:bill:export')")
    @Log(title = "入账列表", businessType = BusinessType.EXPORT)
    @PostMapping("/export")
    public void export(HttpServletResponse response, Bill bill)
    {
        List<Bill> list = billService.selectBillList(bill);
        ExcelUtil<Bill> util = new ExcelUtil<Bill>(Bill.class);
        util.exportExcel(response, list, "入账列表数据");
    }

    /**
     * 获取入账列表详细信息
     */
    @PreAuthorize("@ss.hasPermi('system:bill:query')")
    @GetMapping(value = "/{id}")
    public AjaxResult getInfo(@PathVariable("id") Long id)
    {
        return success(billService.selectBillById(id));
    }

    /**
     * 新增入账列表
     */
    @PreAuthorize("@ss.hasPermi('system:bill:add')")
    @Log(title = "入账列表", businessType = BusinessType.INSERT)
    @PostMapping
    public AjaxResult add(@RequestBody Bill bill)
    {
        return toAjax(billService.insertBill(bill));
    }

    /**
     * 修改入账列表
     */
    @PreAuthorize("@ss.hasPermi('system:bill:edit')")
    @Log(title = "入账列表", businessType = BusinessType.UPDATE)
    @PutMapping
    public AjaxResult edit(@RequestBody Bill bill)
    {
        return toAjax(billService.updateBill(bill));
    }

    /**
     * 删除入账列表
     */
    @PreAuthorize("@ss.hasPermi('system:bill:remove')")
    @Log(title = "入账列表", businessType = BusinessType.DELETE)
	@DeleteMapping("/{ids}")
    public AjaxResult remove(@PathVariable Long[] ids)
    {
        return toAjax(billService.deleteBillByIds(ids));
    }

    /**
     * 手动生成账单
     */
    @PreAuthorize("@ss.hasPermi('system:bill:add')")
    @Log(title = "手动生成账单", businessType = BusinessType.INSERT)
    @PostMapping("/generate")
    public AjaxResult generateBill(@RequestBody Bill bill)
    {
        try
        {
            if (bill.getElderlyId() == null || bill.getBillMonth() == null || bill.getBillMonth().trim().isEmpty())
            {
                return error("老人ID和账单月份不能为空");
            }
            int result = billService.generateBillManually(bill.getElderlyId(), bill.getBillMonth());
            if (result > 0)
            {
                return success("账单生成成功");
            }
            else
            {
                return error("账单生成失败");
            }
        }
        catch (Exception e)
        {
            return error("账单生成失败：" + e.getMessage());
        }
    }

    /**
     * 根据老人ID和退住日期查询退住当月账单（用于账单调整）
     * 根据账单状态返回不同数据：
     * - 如果账单状态是"待支付"或"已关闭"：返回"暂无"
     * - 如果账单状态是"已支付"：返回实际数据
     */
    @PreAuthorize("@ss.hasPermi('system:bill:query')")
    @GetMapping("/checkoutMonth/{elderlyId}/{checkoutDate}")
    public AjaxResult getCheckoutMonthBill(@PathVariable("elderlyId") Long elderlyId,
                                           @PathVariable("checkoutDate") String checkoutDate)
    {
        try {
            System.out.println("=== 查询退住当月账单 ===");
            System.out.println("老人ID: " + elderlyId);
            System.out.println("退住日期: " + checkoutDate);

            // 1. 解析退住日期
            java.text.SimpleDateFormat sdf = new java.text.SimpleDateFormat("yyyy-MM-dd");
            java.util.Date checkoutDateObj = sdf.parse(checkoutDate);
            System.out.println("退住日期对象: " + checkoutDateObj);

            // 2. 提取退住日期的年月（账单月份）
            String billMonth = checkoutDate.substring(0, 7); // 例如：2025-10-24 → 2025-10
            System.out.println("账单月份（从退住日期提取）: " + billMonth);

            // 3. 提取退住日期的天数（实缴天数）
            int dayOfMonth = Integer.parseInt(checkoutDate.substring(8, 10));
            System.out.println("退住日期天数: " + dayOfMonth);

            // 4. 计算当月总天数
            java.util.Calendar cal = java.util.Calendar.getInstance();
            cal.setTime(checkoutDateObj);
            int daysInMonth = cal.getActualMaximum(java.util.Calendar.DAY_OF_MONTH);
            System.out.println("当月总天数: " + daysInMonth);

            // 5. 计算实缴天数和退款天数
            int actualDays = dayOfMonth; // 实缴天数 = 退住日期在当月的天数
            int refundDays = daysInMonth - actualDays; // 退款天数 = 当月总天数 - 实缴天数
            System.out.println("实缴天数: " + actualDays);
            System.out.println("退款天数: " + refundDays);

            // 6. ✅ 查询该老人退住当月的账单（不限制支付状态）
            Bill queryBill = new Bill();
            queryBill.setElderlyId(elderlyId);
            queryBill.setBillMonth(billMonth); // ✅ 退住日期的月份

            System.out.println("=== 查询条件 ===");
            System.out.println("老人ID: " + elderlyId);
            System.out.println("账单月份: " + billMonth + " (必须与退住日期月份一致)");
            System.out.println("支付状态: 不限制（查询所有状态）");

            List<Bill> bills = billService.selectBillList(queryBill);
            System.out.println("查询到的账单数量: " + (bills != null ? bills.size() : 0));

            if (bills != null && !bills.isEmpty()) {
                System.out.println("✅ 找到符合条件的账单，数量: " + bills.size());

                Bill bill = bills.get(0); // 取第一条
                System.out.println("=== 账单详细信息 ===");
                System.out.println("账单ID: " + bill.getId());
                System.out.println("账单编号（bill_no）: " + bill.getBillNo());
                System.out.println("账单月份（bill_month）: " + bill.getBillMonth());
                System.out.println("老人ID（elderly_id）: " + bill.getElderlyId());
                System.out.println("每月应付（monthly_payable）: " + bill.getMonthlyPayable());
                System.out.println("应付金额（payable_amount）: " + bill.getPayableAmount());
                System.out.println("支付状态（transaction_status）: " + bill.getTransactionStatus());
                System.out.println("账单开始时间: " + bill.getBillStartTime());
                System.out.println("账单结束时间: " + bill.getBillEndTime());

                // 7. ✅ 根据账单状态决定返回数据
                String transactionStatus = bill.getTransactionStatus();
                System.out.println("=== 账单状态判断 ===");
                System.out.println("当前账单状态: " + transactionStatus);

                java.util.Map<String, Object> result = new java.util.HashMap<>();
                
                // 账单月份始终是退住日期的年月
                result.put("billMonth", billMonth);
                
                if ("已支付".equals(transactionStatus)) {
                    System.out.println("✅ 账单状态为'已支付'，返回实际数据");
                    
                    // 计算可退金额（按天数比例）
                    java.math.BigDecimal monthlyAmount = bill.getMonthlyPayable() != null ?
                        bill.getMonthlyPayable() : bill.getPayableAmount();

                    if (monthlyAmount != null) {
                        // 可退金额 = 每月应付 * (退款天数 / 当月总天数)
                        java.math.BigDecimal refundAmount = monthlyAmount
                            .multiply(new java.math.BigDecimal(refundDays))
                            .divide(new java.math.BigDecimal(daysInMonth), 2, java.math.BigDecimal.ROUND_HALF_UP);

                        System.out.println("每月应付: " + monthlyAmount);
                        System.out.println("可退金额: " + refundAmount);

                        result.put("billNo", bill.getBillNo());              // ✅ 实际账单编号
                        result.put("monthlyPayable", monthlyAmount);
                        result.put("refundableAmount", refundAmount);
                        result.put("actualDays", actualDays);                // ✅ 退住日期在当月已度过的天数
                        result.put("refundDays", refundDays);                // ✅ 退住日期当月还剩下的天数
                        result.put("daysInMonth", daysInMonth);
                        result.put("billData", bill);
                        result.put("status", "已支付");

                        System.out.println("=== 返回实际数据 ===");
                        System.out.println("billNo（账单编号）: " + bill.getBillNo());
                        System.out.println("billMonth（账单月份）: " + billMonth);
                        System.out.println("actualDays（实缴天数）: " + actualDays);
                        System.out.println("refundDays（退款天数）: " + refundDays);
                        System.out.println("refundableAmount（可退金额）: " + refundAmount);
                    } else {
                        return error("账单金额为空");
                    }
                } else if ("待支付".equals(transactionStatus) || "已关闭".equals(transactionStatus)) {
                    System.out.println("✅ 账单状态为'" + transactionStatus + "'，返回暂无数据");
                    
                    result.put("billNo", "暂无");
                    result.put("monthlyPayable", 0);
                    result.put("refundableAmount", 0);
                    result.put("actualDays", 0);
                    result.put("refundDays", 0);
                    result.put("daysInMonth", daysInMonth);
                    result.put("billData", bill);
                    result.put("status", transactionStatus);

                    System.out.println("=== 返回暂无数据 ===");
                    System.out.println("billNo（账单编号）: 暂无");
                    System.out.println("billMonth（账单月份）: " + billMonth);
                    System.out.println("actualDays（实缴天数）: 0");
                    System.out.println("refundDays（退款天数）: 0");
                    System.out.println("refundableAmount（可退金额）: 0");
                } else {
                    System.out.println("⚠️ 未知账单状态: " + transactionStatus + "，返回暂无数据");
                    
                    result.put("billNo", "暂无");
                    result.put("monthlyPayable", 0);
                    result.put("refundableAmount", 0);
                    result.put("actualDays", 0);
                    result.put("refundDays", 0);
                    result.put("daysInMonth", daysInMonth);
                    result.put("billData", bill);
                    result.put("status", transactionStatus);
                }

                System.out.println("=== 账单查询完成 ===");
                return success(result);
            } else {
                System.out.println("未找到" + billMonth + "月的账单，返回暂无数据");
                
                // 即使没有找到账单，也返回账单月份信息
                java.util.Map<String, Object> result = new java.util.HashMap<>();
                result.put("billNo", "暂无");
                result.put("billMonth", billMonth);
                result.put("monthlyPayable", 0);
                result.put("refundableAmount", 0);
                result.put("actualDays", 0);
                result.put("refundDays", 0);
                result.put("daysInMonth", daysInMonth);
                result.put("billData", null);
                result.put("status", "无账单");
                
                return success(result);
            }

        } catch (Exception e) {
            System.out.println("查询账单异常: " + e.getMessage());
            e.printStackTrace();
            return error("查询账单失败：" + e.getMessage());
        }
    }

    /**
     * 根据老人ID查询待支付账单（用于账单调整的欠费卡片）
     */
    @PreAuthorize("@ss.hasPermi('system:bill:query')")
    @GetMapping("/overdueBills/{elderlyId}")
    public AjaxResult getOverdueBills(@PathVariable("elderlyId") Long elderlyId)
    {
        try {
            System.out.println("=== 查询老人待支付账单 ===");
            System.out.println("老人ID: " + elderlyId);

            // 查询条件：老人ID + 支付状态为"待支付"
            Bill queryBill = new Bill();
            queryBill.setElderlyId(elderlyId);
            queryBill.setTransactionStatus("待支付");

            System.out.println("=== 查询条件 ===");
            System.out.println("老人ID: " + elderlyId);
            System.out.println("支付状态: 待支付");

            List<Bill> bills = billService.selectBillList(queryBill);
            System.out.println("查询到的待支付账单数量: " + (bills != null ? bills.size() : 0));

            if (bills != null && !bills.isEmpty()) {
                System.out.println("✅ 找到待支付账单，数量: " + bills.size());

                // 构建返回数据列表
                java.util.List<java.util.Map<String, Object>> resultList = new java.util.ArrayList<>();
                
                for (Bill bill : bills) {
                    System.out.println("=== 账单详细信息 ===");
                    System.out.println("账单ID: " + bill.getId());
                    System.out.println("账单编号（bill_no）: " + bill.getBillNo());
                    System.out.println("账单月份（bill_month）: " + bill.getBillMonth());
                    System.out.println("应付金额（payable_amount）: " + bill.getPayableAmount());
                    System.out.println("支付状态（transaction_status）: " + bill.getTransactionStatus());

                    java.util.Map<String, Object> billData = new java.util.HashMap<>();
                    billData.put("billNo", bill.getBillNo());              // 账单编号
                    billData.put("billMonth", bill.getBillMonth());        // 账单月份
                    billData.put("payableAmount", bill.getPayableAmount()); // 应付金额
                    billData.put("status", bill.getTransactionStatus());   // 支付状态
                    
                    resultList.add(billData);
                }

                System.out.println("=== 返回数据 ===");
                System.out.println("待支付账单数量: " + resultList.size());
                for (java.util.Map<String, Object> billData : resultList) {
                    System.out.println("账单编号: " + billData.get("billNo"));
                    System.out.println("账单月份: " + billData.get("billMonth"));
                    System.out.println("应付金额: " + billData.get("payableAmount"));
                }
                System.out.println("=== 待支付账单查询完成 ===");
                
                return success(resultList);
            } else {
                System.out.println("未找到待支付账单");
                return success(new java.util.ArrayList<>());
            }

        } catch (Exception e) {
            System.out.println("查询待支付账单异常: " + e.getMessage());
            e.printStackTrace();
            return error("查询待支付账单失败：" + e.getMessage());
        }
    }
}
